grammar UpdateQueryLangOnly;

query 	:	'UPDATE' kind 'SET' a1=assign (',' a2=assign)* ('WHERE' where)? (u=using)*
	;

using	:	'USING' kind 'WHERE' where
	;

where	:	condition
	| 	condition 'AND' w1=where
	;

condition
	:	'__key__' '=' expr
	|	'__key__' '=' property
	|	property '=' expr
	|	property '<' expr
	|	property '<=' expr
	|	property '>' expr
	|	property '>=' expr
	|	p1=property '=' p2=property
	;

kind	:	kindName=ID (alias=ID) ? 
	;

assign	: 	property '=' assignExpr;

assignExpr
	:	e1=atom '+' e2=assignExpr
	|	e1=atom '-' e2=assignExpr
	|	e1=atom 'CONCAT' e2=assignExpr
	| 	'(' a=assignExpr ')'
	|	atom
	;

atom    : 	INT
    	| 	STRING
    	| 	property { $value = $property.prop; }
    	;

argumentList
	:	(a1=assignExpr (',' a2=assignExpr )*)?
	;

property
	:	(alias=ID '.')? propertyName=ID
	;

expr
	:	STRING
	|	INT
	|	FLOAT
	;


ID  :	('a'..'z'|'A'..'Z'|'_') ('a'..'z'|'A'..'Z'|'0'..'9'|'_')*
    ;

INT :	'0'..'9'+
    ;

FLOAT
    :   ('0'..'9')+ '.' ('0'..'9')* EXPONENT?
    |   '.' ('0'..'9')+ EXPONENT?
    |   ('0'..'9')+ EXPONENT
    ;

STRING
    :  '"' ( ESC_SEQ | ~('\\'|'"') )* '"'
    ;

fragment
EXPONENT : ('e'|'E') ('+'|'-')? ('0'..'9')+ ;

fragment
HEX_DIGIT : ('0'..'9'|'a'..'f'|'A'..'F') ;

fragment
ESC_SEQ
    :   '\\' ('b'|'t'|'n'|'f'|'r'|'\"'|'\''|'\\')
    |   UNICODE_ESC
    |   OCTAL_ESC
    ;

fragment
OCTAL_ESC
    :   '\\' ('0'..'3') ('0'..'7') ('0'..'7')
    |   '\\' ('0'..'7') ('0'..'7')
    |   '\\' ('0'..'7')
    ;

fragment
UNICODE_ESC
    :   '\\' 'u' HEX_DIGIT HEX_DIGIT HEX_DIGIT HEX_DIGIT
    ;
